//----------------------------------------------------------------------------//
//                                                                            //
// ozz-animation is hosted at http://github.com/guillaumeblanc/ozz-animation  //
// and distributed under the MIT License (MIT).                               //
//                                                                            //
// Copyright (c) Guillaume Blanc                                              //
//                                                                            //
// Permission is hereby granted, free of charge, to any person obtaining a    //
// copy of this software and associated documentation files (the "Software"), //
// to deal in the Software without restriction, including without limitation  //
// the rights to use, copy, modify, merge, publish, distribute, sublicense,   //
// and/or sell copies of the Software, and to permit persons to whom the      //
// Software is furnished to do so, subject to the following conditions:       //
//                                                                            //
// The above copyright notice and this permission notice shall be included in //
// all copies or substantial portions of the Software.                        //
//                                                                            //
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR //
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,   //
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL    //
// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER //
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING    //
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER        //
// DEALINGS IN THE SOFTWARE.                                                  //
//                                                                            //
//----------------------------------------------------------------------------//

#ifndef OZZ_OZZ_ANIMATION_OFFLINE_TOOLS_IMPORT2OZZ_H_
#define OZZ_OZZ_ANIMATION_OFFLINE_TOOLS_IMPORT2OZZ_H_

#include "SkrAnimTool/ozz/tools/export.h"

#include "SkrAnim/ozz/base/containers/string.h"
#include "SkrAnim/ozz/base/containers/vector.h"

#include "SkrAnimTool/ozz/raw_animation.h"
#include "SkrAnimTool/ozz/raw_skeleton.h"
#include "SkrAnimTool/ozz/raw_track.h"

#include "SkrAnim/ozz/base/platform.h"

namespace ozz
{
namespace animation
{

class Skeleton;

namespace offline
{

// Defines ozz converter/importer interface.
// OzzImporter implements a command line tool to convert any source data format
// to ozz skeletons and animations. The tool exposes a set of global options
// through the command line, and a json configuration file to tune import
// settings. Reference json configuration is generated at
// src\animation\offline\tools\reference.json.
// To import a new source data format, one will implement the pure virtual
// functions of this interface. All the conversions end error processing are
// done by the tool.
class OZZ_ANIMTOOLS_DLL OzzImporter
{

public:
    virtual ~OzzImporter() {}

    // Function operator that must be called with main() arguments to start import
    // process.
    int operator()(int _argc, const char** _argv);

    // Loads source data file.
    // Returning false will report and error.
    virtual bool Load(const char* _filename) = 0;

    // Skeleton management.

    // Defines node types that should be considered as skeleton joints.
    struct NodeType
    {
        bool skeleton : 1; // Uses skeleton nodes as skeleton joints.
        bool marker : 1;   // Uses marker nodes as skeleton joints.
        bool camera : 1;   // Uses camera nodes as skeleton joints.
        bool geometry : 1; // Uses geometry nodes as skeleton joints.
        bool light : 1;    // Uses light nodes as skeleton joints.
        bool null : 1;     // Uses null nodes as skeleton joints.
        bool any : 1;      // Uses any node type as skeleton joints, including those
                           // listed above and any other.
    };

    // Import a skeleton from the source data file.
    // Returning false will report and error.
    virtual bool Import(ozz::animation::offline::RawSkeleton* _skeleton, const NodeType& _types) = 0;

    // Animations management.

    // Gets the name of all the animations/clips/takes available from the source
    // data file.
    typedef ozz::vector<ozz::string> AnimationNames;
    virtual AnimationNames GetAnimationNames() = 0;

    // Import animation "_animation_name" from the source data file.
    // The skeleton is provided such that implementation can look for its joints
    // animations.
    // Returning false will report and error.
    virtual bool Import(const char* _animation_name, const ozz::animation::Skeleton& _skeleton, float _sampling_rate, RawAnimation* _animation) = 0;

    // Tracks / properties management.

    // Defines properties, aka user-channel data: animations that aren't only
    // joint transforms.
    struct NodeProperty
    {
        ozz::string name;

        enum Type
        {
            kFloat1,
            kFloat2,
            kFloat3,
            kFloat4,
            kPoint,
            kVector
        };
        Type type;
    };

    // Get all properties available for a node.
    typedef ozz::vector<NodeProperty> NodeProperties;
    virtual NodeProperties GetNodeProperties(const char* _node_name) = 0;

    // Imports a track of type 1, 2, 3 or 4 floats, for the triplet
    // _animation_name/_node_name/_track_name.
    // Returning false will report and error.
    virtual bool Import(const char* _animation_name, const char* _node_name, const char* _track_name, NodeProperty::Type _track_type, float _sampling_rate, RawFloatTrack* _track) = 0;
    virtual bool Import(const char* _animation_name, const char* _node_name, const char* _track_name, NodeProperty::Type _track_type, float _sampling_rate, RawFloat2Track* _track) = 0;
    virtual bool Import(const char* _animation_name, const char* _node_name, const char* _track_name, NodeProperty::Type _track_type, float _sampling_rate, RawFloat3Track* _track) = 0;
    virtual bool Import(const char* _animation_name, const char* _node_name, const char* _track_name, NodeProperty::Type _track_type, float _sampling_rate, RawFloat4Track* _track) = 0;

    // Build a filename from a wildcard string.
    ozz::string BuildFilename(const char* _filename,
        const char* _data_name) const;
};
} // namespace offline
} // namespace animation
} // namespace ozz
#endif // OZZ_OZZ_ANIMATION_OFFLINE_TOOLS_IMPORT2OZZ_H_
